package zero.tech.games.mj.util;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

import zero.tech.games.mj.data.MjConfig;

/**
 * 麻将胡牌工具类
 * @author Administrator
 *
 */
public class MjHuUtil {
	
	/**
	 * 胡牌
	 * @param cards 玩家手牌
	 * @param gui 玩家手中的鬼牌
	 * @param type 胡牌类型 1,平胡：2，对对胡；3，七对；4，幺久牌；
	 * @return
	 */
	public static boolean checkHu(List<Integer> card, List<Integer> gui, boolean isAllGui, MjConfig mjConfig) {
		List<Integer> guis = getTemporary(gui);
		List<Integer> cards = getTemporary(card);
		boolean result = false;
		// 检测全鬼牌胡
		if (isAllGui && guis.size() >= 4) {
			return true;
		}
		if (!result && mjConfig.getQiduiHu() == 1) {
			result = tryHu(cards, guis);
		}
		if (!result) {
			result = tryHuAAA(cards, guis);
		}
		if (!result) {
			if (guis.size() + cards.size() == 14) {
				result = tryHuAABBCC(cards, guis);
			}
		}
		return result;
	}

	/**
	 * 临时集合
	 * @param card
	 * @return
	 */
	public static List<Integer> getTemporary(List<Integer> card) {
		List<Integer> arr = new ArrayList<Integer>();
		for (int car : card) {
			arr.add(car);
		}
		return arr;
	}

	/**
	 * 获取并移除手中的风牌
	 * @param card 手牌
	 * @return 获取的风牌
	 */
	public static List<Integer> getWindList(List<Integer> cards) {
		List<Integer> car = new ArrayList<Integer>();
		for (int i = 0; i < cards.size(); i++) {
			int[] Card = CardUtil.getCard(cards.get(i));
			if (Card[3] == 3) {
				car.add(cards.remove(i));
				i--;
			}
		}
		return car;
	}

	/**
	 * 排序
	 * @param list 牌
	 * @return
	 */
	public static void getNewList(List<Integer> list) {
		// 处理顺序问题 顺序
		Collections.sort(list, new Comparator<Integer>() {
			@Override
			public int compare(Integer o1, Integer o2) {
				int[] Card1 = CardUtil.getCard(o1);
				int[] Card2 = CardUtil.getCard(o2);
				if (Card1[1] > Card2[1] && Card1[3] == Card2[3]) {
					return 1;
				} else if (Card1[3] > Card2[3]) {
					return 1;
				}
				return -1;
			}
		});
	}

	/**
	 * 检测牌 平胡
	 * @param card 手牌
	 * @param gui 鬼牌
	 * @return
	 */
	private static boolean tryHu(List<Integer> card, List<Integer> gui) {
		getNewList(card);
		if (card.size() == 0 || (card.size() == 7 && gui.size() == 7)
				|| (card.size() == 3 && gui.size() == 5)
				|| (card.size() == 2 && gui.size() == 3)
				|| (card.size() == 1 && gui.size() >= 1)) {
			if (card.size() > 0 && gui.size() > 0) {
				gui.clear();
			}
			return true;
		}
		if (card.size() % 3 == 2 && gui.size() == 0) {// 说明对牌没出现 并且没有癞子
			for (int i = 0; i < card.size() - 1; i++) {
				int[] card1 = CardUtil.getCard(card.get(i));
				int[] card2 = CardUtil.getCard(card.get(i + 1));
				if (card1[3] == card2[3] && card1[1] == card2[1]) {
					List<Integer> Pai = new ArrayList<Integer>();
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					if (tryHu(card, gui)) {
						return true;
					}
					for (int car : Pai) {
						card.add(car);
					}
					getNewList(card);
				}
			}
		} else {
			// 三个一样的
			for (int i = 0; i < card.size() - 2; i++) {
				int[] card1 = CardUtil.getCard(card.get(i));
				int[] card2 = CardUtil.getCard(card.get(i + 1));
				int[] card3 = CardUtil.getCard(card.get(i + 2));
				if (card1[3] == card2[3] && card2[3] == card3[3]
						&& card1[1] == card2[1] && card2[1] == card3[1]) {
					List<Integer> Pai = new ArrayList<Integer>();
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					if (tryHu(card, gui)) {
						return true;
					}
					for (int car : Pai) {
						card.add(car);
					}
					getNewList(card);
				}
			}
			getNewList(card);
			// 是否是顺子
			for (int i = 0; i < card.size() - 2; i++) {
				List<Integer> list = new ArrayList<Integer>();
				for (int j = 0; j < card.size() - 1; j++) {
					int[] value1 = CardUtil.getCard(card.get(j));
					int[] value2 = CardUtil.getCard(card.get(j + 1));
					if (value1[1] == value2[1] && value1[3] == value2[3]) {
						list.add(card.remove(j));
						j--;
					}
				}
				for (int car : list) {
					card.add(car);
				}
				List<Integer> listt = new ArrayList<Integer>();
				for (int j = 0; j < card.size() - 1; j++) {
					int[] value1 = CardUtil.getCard(card.get(j));
					int[] value2 = CardUtil.getCard(card.get(j + 1));
					if (value1[1] == value2[1] && value1[3] == value2[3]) {
						listt.add(card.remove(j));
						j--;
					}
				}
				for (int car : listt) {
					card.add(car);
				}
				int[] card1 = CardUtil.getCard(card.get(i));
				int[] card2 = CardUtil.getCard(card.get(i + 1));
				int[] card3 = CardUtil.getCard(card.get(i + 2));
				if (card1[3] == card2[3] && card2[3] == card3[3]
						&& card1[1] == (card2[1] - 1)
						&& card2[1] == (card3[1] - 1) && card1[3] != 3) {
					List<Integer> Pai = new ArrayList<Integer>();
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					if (tryHu(card, gui)) {
						return true;
					}
					for (int car : Pai) {
						card.add(car);
					}
					getNewList(card);
				}
			}
			if (gui.size() > 0) {
				getNewList(card);
				// 补AAA癞子
				for (int i = 0; i < card.size() - 1; i++) {
					int[] value1 = CardUtil.getCard(card.get(i));
					int[] value2 = CardUtil.getCard(card.get(i + 1));
					if (value2[1] == value1[1] && value2[3] == value1[3]
							&& gui.size() > 0) {
						List<Integer> Pai = new ArrayList<Integer>();
						List<Integer> PaiGui = new ArrayList<Integer>();
						Pai.add(card.remove(i));
						Pai.add(card.remove(i));
						PaiGui.add(gui.remove(0));
						if (tryHu(card, gui)) {
							return true;
						}
						for (int car : Pai) {
							card.add(car);
						}
						for (int car : PaiGui) {
							gui.add(car);
						}
						getNewList(card);
					}
				}
				getNewList(card);
				// 补ABC癞子
				for (int i = 0; i < card.size() - 1; i++) {
					List<Integer> list = new ArrayList<Integer>();
					for (int j = 0; j < card.size() - 1; j++) {
						int[] value1 = CardUtil.getCard(card.get(j));
						int[] value2 = CardUtil.getCard(card.get(j + 1));
						if (value1[1] == value2[1] && value1[3] == value2[3]) {
							list.add(card.remove(j));
							j--;
						}
					}
					for (int car : list) {
						card.add(car);
					}
					int[] value1 = CardUtil.getCard(card.get(i));
					int[] value2 = CardUtil.getCard(card.get(i + 1));
					if (value2[3] == value1[3]
							&& (value2[1] - value1[1] == 2 || value2[1]
									- value1[1] == 1) && gui.size() > 0
							&& value1[3] != 3) {
						List<Integer> Pai = new ArrayList<Integer>();
						List<Integer> PaiGui = new ArrayList<Integer>();
						Pai.add(card.remove(i));
						Pai.add(card.remove(i));
						PaiGui.add(gui.remove(0));
						if (tryHu(card, gui)) {
							return true;
						}
						for (int car : Pai) {
							card.add(car);
						}
						for (int car : PaiGui) {
							gui.add(car);
						}
						getNewList(card);
					}
				}

			}
		}
		return false;
	}

	/**
	 * 检测牌 对对胡
	 * 
	 * @param card
	 *            手牌
	 * @param gui
	 *            鬼牌
	 * @return
	 */
	private static boolean tryHuAAA(List<Integer> card, List<Integer> gui) {
		getNewList(card);
		if (card.size() == 0 || (card.size() == 3 && gui.size() == 5)
				|| (card.size() == 2 && gui.size() == 3)
				|| (card.size() == 1 && gui.size() >= 1)) {
			if (card.size() > 0 && gui.size() > 0) {
				gui.clear();
			}
			return true;
		}
		if (card.size() % 3 == 2 && gui.size() == 0) {// 说明对牌没出现 并且没有癞子
			for (int i = 0; i < card.size() - 1; i++) {
				int[] card1 = CardUtil.getCard(card.get(i));
				int[] card2 = CardUtil.getCard(card.get(i + 1));
				if (card1[3] == card2[3] && card1[1] == card2[1]) {
					List<Integer> Pai = new ArrayList<Integer>();
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					if (tryHuAAA(card, gui)) {
						return true;
					}
					for (int car : Pai) {
						card.add(car);
					}
					getNewList(card);
				}
			}
		} else {
			// 三个一样的
			for (int i = 0; i < card.size() - 2; i++) {
				int[] card1 = CardUtil.getCard(card.get(i));
				int[] card2 = CardUtil.getCard(card.get(i + 1));
				int[] card3 = CardUtil.getCard(card.get(i + 2));
				if (card1[3] == card2[3] && card2[3] == card3[3]
						&& card1[1] == card2[1] && card2[1] == card3[1]) {
					List<Integer> Pai = new ArrayList<Integer>();
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					Pai.add(card.remove(i));
					if (tryHuAAA(card, gui)) {
						return true;
					}
					for (int car : Pai) {
						card.add(car);
					}
					getNewList(card);
				}
			}
			if (gui.size() > 0) {
				getNewList(card);
				// 补AAA癞子
				for (int i = 0; i < card.size() - 1; i++) {
					int[] value1 = CardUtil.getCard(card.get(i));
					int[] value2 = CardUtil.getCard(card.get(i + 1));
					if (value2[1] == value1[1] && value2[3] == value1[3]
							&& gui.size() > 0) {
						List<Integer> Pai = new ArrayList<Integer>();
						List<Integer> PaiGui = new ArrayList<Integer>();
						Pai.add(card.remove(i));
						Pai.add(card.remove(i));
						PaiGui.add(gui.remove(0));
						if (tryHuAAA(card, gui)) {
							return true;
						}
						for (int car : Pai) {
							card.add(car);
						}
						for (int car : PaiGui) {
							gui.add(car);
						}
						getNewList(card);
					}
				}
			}
		}
		return false;
	}
	
	/**
	 * 检测牌 七对
	 * 
	 * @param card 手牌
	 * @param gui 鬼牌
	 * @return
	 */
	private static boolean tryHuAABBCC(List<Integer> card, List<Integer> gui) {
		getNewList(card);
		if (card.size() == 0 || (card.size() == 7 && gui.size() == 7)
				|| (card.size() == 6 && gui.size() == 6)
				|| (card.size() == 5 && gui.size() == 5)
				|| (card.size() == 4 && gui.size() == 4)
				|| (card.size() == 3 && gui.size() == 3)
				|| (card.size() == 2 && gui.size() == 2)
				|| (card.size() == 1 && gui.size() >= 1)) {
			if (card.size() > 0 && gui.size() > 0) {
				gui.clear();
			}
			return true;
		}
		for (int i = 0; i < card.size() - 1; i++) {
			int[] card1 = CardUtil.getCard(card.get(i));
			int[] card2 = CardUtil.getCard(card.get(i + 1));
			if (card1[3] == card2[3] && card1[1] == card2[1]) {
				List<Integer> Pai = new ArrayList<Integer>();
				Pai.add(card.remove(i));
				Pai.add(card.remove(i));
				if (tryHuAABBCC(card, gui)) {
					return true;
				}
				for (int car : Pai) {
					card.add(car);
				}
				getNewList(card);
			}
		}
		if (gui.size() > 0) {
			getNewList(card);
			for (int i = 0; i < card.size(); i++) {
				List<Integer> Pai = new ArrayList<Integer>();
				List<Integer> PaiGui = new ArrayList<Integer>();
				Pai.add(card.remove(i));
				PaiGui.add(gui.remove(0));
				if (tryHuAABBCC(card, gui)) {
					return true;
				}
				for (int car : Pai) {
					card.add(car);
				}
				for (int car : PaiGui) {
					gui.add(car);
				}
				getNewList(card);
			}
		}
		return false;
	}

}
